package com.cskaoyan.aspect;

import com.cskaoyan.bean.PO.MarketAdmin;
import com.cskaoyan.bean.PO.MarketLog;
import com.cskaoyan.bean.PO.MarketOrder;
import com.cskaoyan.exception.ValidationException;
import com.cskaoyan.service.AdminLogService;
import com.cskaoyan.utils.ValidationUtil;
import org.apache.shiro.SecurityUtils;
import org.apache.shiro.session.Session;
import org.apache.shiro.subject.Subject;
import org.aspectj.lang.JoinPoint;
import org.aspectj.lang.annotation.*;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;
import org.springframework.validation.BindingResult;

import java.util.Date;


/**
 * @ClassName CustomAspect
 * @Description
 * @Author Lxz
 * @Date 2022-8-13 23:40
 */
@Aspect
@Component
public class CustomAspect {
    @Autowired
    AdminLogService adminLogService;


    @Pointcut("execution(* com..controller..*Log(..))")
    public void controllerPoint() {
    }
    @Pointcut("execution(* com..AdminAuthController.log*(..))")
    public void adminAuthConrollerPoint() {
    }

    @After("controllerPoint()")
    public void insertLogAfterHandle(JoinPoint joinPoint) {
        Subject subject = SecurityUtils.getSubject();
//        String username = (String) subject.getPrincipal();
//        MarketAdmin marketAdmin = new MarketAdmin();
//        marketAdmin.setUsername(username);
//        MarketAdmin adminInfo = adminLogService.getAdminInfo(marketAdmin);

//        MarketAdmin primaryPrincipal = (MarketAdmin) subject.getPrincipals().getPrimaryPrincipal();
//        MarketAdmin adminInfo = adminLogService.getAdminInfo(primaryPrincipal);

        Session session = SecurityUtils.getSubject().getSession();

        String admin = (String) session.getAttribute("logAdmin");
        MarketAdmin marketAdmin = new MarketAdmin();
        marketAdmin.setUsername(admin);
        MarketAdmin adminInfo = adminLogService.getAdminInfo(marketAdmin);

        String ip = adminInfo.getLastLoginIp();
        Date addTime = adminInfo.getAddTime();
        Date updateTime = adminInfo.getUpdateTime();
        Integer logType = (Integer) session.getAttribute("logType");
        String logAction = (String) session.getAttribute("logAction");
        boolean logStatus = (boolean) session.getAttribute("logStatus");
        String logResult = (String) session.getAttribute("logResult");
        String logComment = (String) session.getAttribute("logComment");

        if (("删除订单".equals(logAction) || "发货".equals(logAction) || "退款".equals(logAction)) && logStatus ) {
            Integer logOrderId = (Integer) session.getAttribute("logOrderId");
            MarketOrder marketOrder = new MarketOrder();
            marketOrder.setId(logOrderId);
            MarketOrder orderInfo = adminLogService.getOrderInfo(marketOrder);
            String orderSn = orderInfo.getOrderSn();
            logResult = orderSn;
        }

        MarketLog marketLog = new MarketLog();
        marketLog.setAdmin(admin);
        marketLog.setIp(ip);
        marketLog.setType(logType);
        marketLog.setAction(logAction);
        marketLog.setStatus(logStatus);
        marketLog.setResult(logResult);
        marketLog.setComment(logComment);
        marketLog.setAddTime(addTime);
        marketLog.setUpdateTime(updateTime);
        marketLog.setDeleted(false);
        adminLogService.insertLog(marketLog);
        session.removeAttribute("logType");
        session.removeAttribute("logAction");
        session.removeAttribute("logStatus");
        session.removeAttribute("logResult");
        session.removeAttribute("logComment");
        if ("退出".equals(logAction)) {
            subject.logout();
        }
    }


    /**
     * 一、确定什么时候进行增强        before
     * 二、怎么增强，切面表达式or注解  注解
     */
    @Before("@annotation(com.cskaoyan.aspect.ValidateParameter)")
    public void validateParameter(JoinPoint joinPoint) throws ValidationException {
        // 首先拿到，handler方法里是否存在 bindingResult（校验结果） 形参
        // 有的话拿过来,进行判断，无的话，就要给他报错。 加了注解不写形参--报错
        Object[] args = joinPoint.getArgs();
        if (args == null || args.length == 0) {
            // 抛出异常，参数校验里，要加上bindingResult形参
            throw new ValidationException("形参必须有bindingResult校验结果！");
        }
        boolean flag = true;
        for (Object arg : args) {
            if (arg instanceof BindingResult) {
                ValidationUtil.valid((BindingResult) arg);
                flag = false;
            }
        }
        if (flag) {
            // 不存在这个bindingResult形参
            throw new ValidationException("形参必须有bindingResult校验结果！");
        }
    }
}
